%options escape=$
%options la=2
%options fp=MTParser,prefix=TK_
%options noserialize
%options package=edu.pku.sei.transformation.mtparser
%options import_terminals=MTLexer.g
%options template=dtParserTemplateF.gi
%options ast_directory=./,automatic_ast=toplevel,var=nt,visitor=default

%Start
	goal
%End

%KeyWords
foreach forall existone

new delete

if then else endif

and or not

check enforce match full partial

transformation rule env trace

null invalid

def based

true false

evaluate

exclusiveVars

union

%End


%Identifier
    IDENTIFIER
%End

%Terminals
    
    INTEGER_LITERAL REAL_LITERAL STRING_LITERAL
    
--    PLUS     ::= '+'
--    MINUS    ::= '-'
--    MULTIPLY ::= '*'
--    DIVIDE   ::= '/'

    GREATER       ::= '>'
    LESS          ::= '<'
    EQUAL         ::= '='
--    GREATER_EQUAL ::= '>='
--    LESS_EQUAL    ::= '<='
--    NOT_EQUAL     ::= '<>'

    LPAREN   ::= '('
    RPAREN   ::= ')'
    LBRACE   ::= '{'
    RBRACE   ::= '}'
    LBRACKET ::= '['
    RBRACKET ::= ']'

    ARROW      ::= '->'
    BAR        ::= '|'
    COMMA      ::= ','
    COLON      ::= ':'
    COLONCOLON ::= '::'
    SEMICOLON  ::= ';'
    DOT        ::= '.'
--    DOTDOT     ::= '..'
%End


%Rules
	goal ::= RuleSemantics
	
	RuleSemantics ::= RuleSemantics BasicRuleSemantics | BasicRuleSemantics
	
	BasicRuleSemantics ::= def rule MODE '{' RuleSemanticsBody '}'
	
	MODE ::= SimpleMode | ExtendMode
	
	SimpleMode$CheckMode ::= check 

	SimpleMode$EnforceMode ::= enforce
	
	ExtendMode ::= Name based SimpleMode
	
	ModeName ::= SimpleMode | Name
	
	RuleSemanticsBody ::= Expression
	
	Expression ::= CommaExpr | SingleExpr
	
	CommaExpr ::= Expression ';' SingleExpr
	
	SingleExpr ::= LogicSemanticsExpr | IfExpr | '{' CommaExpr '}'
	
	IfExpr ::= if LogicSemanticsExpr then SingleExpr endif
	
	IfExpr ::= if LogicSemanticsExpr then SingleExpr else SingleExpr endif
	
	LogicSemanticsExpr ::= AndExpr | OrExpr | BooleanExpr
	
	AndExpr ::= BooleanExpr$LeftExpr and BooleanExpr$RightExpr
	
	OrExpr ::= BooleanExpr$LeftExpr or BooleanExpr$RightExpr
	
	BooleanExpr ::= NotExpr | ExistoneExpr | ForallExpr | BasicBooleanExpr
	
	NotExpr ::= not BooleanExpr
	
	ExistoneExpr ::= AtomicExpr '->' existone '{' Name '|'  Expression '}'
	
	ForallExpr ::= AtomicExpr '->' forall '{' Name '|' Expression '}'
	
	BasicBooleanExpr ::= EqualExpr | BooleanFactorExpr
	
	EqualExpr ::= BooleanFactorExpr$LeftExpr '=' BooleanFactorExpr$RightExpr
	
	BooleanFactorExpr ::=  EvalExpr | OperationSemanticsExpr
	
	--ParenBooleanExpr ::= '(' Expression ')'
	
	EvalExpr ::= evaluate '(' AtomicExpr$DomainPart ',' UserDefinedVarExpr$BaseContextPar ',' ModeName ')'
	
	ExclusiveExpr ::= exclusiveVars '(' AtomicExpr$DomainPart ',' AtomicExpr$DomainListPart ',' AtomicExpr$EnvPart ')'
	
	UnionExpr ::= union '(' AtomicExpr$FirstPart ',' AtomicExpr$SecoundPart ')'
	
	OperationSemanticsExpr ::= AtomicExpr | NewExpr | DeleteExpr | AssignExpr
	
	AssignExpr ::= Name '::' '=' OperationSemanticsExpr
	
	NewExpr ::= new '(' AtomicExpr$VarPart ',' AtomicExpr$ModelPart ',' AtomicExpr$DomainPart ',' UserDefinedVarExpr$BaseContextPart ')'
	
	DeleteExpr ::= delete '(' AtomicExpr ')'
	
	AtomicExpr ::=  MatchExpr  | AttributeExpr | OperationExpr | VariableExpr | ConstExpr | ParenAtomicExpr | ExclusiveExpr | UnionExpr
	
	ParenAtomicExpr ::= '(' Expression ')'
	
	VariableExpr ::= PredefinedVarExpr | UserDefinedVarExpr
	
	PredefinedVarExpr ::= transformation | rule | env | trace
	
	UserDefinedVarExpr ::= IDENTIFIER
	
	Name ::= IDENTIFIER
	
	ConstExpr ::= StringConst | IntConst | RealConst | NullConst | InvalidConst | BooleanConst
	
	BooleanConst ::= true | false
	StringConst ::= STRING_LITERAL
	IntConst ::= INTEGER_LITERAL
	RealConst ::= REAL_LITERAL
	NullConst ::= null
	InvalidConst ::= invalid
	
	MatchExpr$FullMatchExpr ::= match '[' full ']' '(' AtomicExpr$DomainPart ',' UserDefinedVarExpr$BaseContextPart ')'
	
	MatchExpr$PartialMatchExpr ::= match '[' partial ']' '(' AtomicExpr$DomainPart ',' UserDefinedVarExpr$BaseContextPart ')'
	
	AttributeExpr ::= AtomicExpr '.' Name
	
	OperationExpr ::= AtomicExpr '.' Name '(' Params ')'
	
	Params ::= Params ',' Param | Param | %empty
	
	Param ::= OperationSemanticsExpr
	
	
%End